package simtester.server

import simtester.server.User

class UserController {

    def index() {

        
    }
    
    def login() {
        if (User.findByUsernameAndPassword(params.username, params.password.encodeAsMD5())) {
            flash.message = 'Login succeeded'
            session.user = params.username
			redirect (action: 'home')
        } else {
            flash.error = 'Login failed'
            redirect (action: 'index')
        }
    }
    
    def logout() {
        session.user = null
        redirect (action: 'index')
    }
    
    def register() {
        // Register the user
        if (request.method == 'POST') {
            def pwNotMatching = false
            if (params.password != params.password_confirmation) {
                flash.error = 'Passwords do not match'
                pwNotMatching = true
            }

			def team = Team.findByName(params.team.toLowerCase())
			
            def user = new User(username: params.username, password: params.password.encodeAsMD5())
            team.addToUsers(user)
			
            if (pwNotMatching || team.hasErrors() || !user.validate() || !team.validate()) {
                render (view: 'register', model: [user: user, teams: Team.list(sort: 'name').collect { it.name.capitalize() }])
            } else {
                team.save(flush: true, failOnError: true)
				createDefaultTestCaseFor(team, user)
	            flash.message = "User ${user.username} created successfully!"
                session.user = params.username
			    redirect (action: 'home')
			}
        } else {
            [teams: Team.list(sort: 'name').collect { it.name.capitalize() }]
        }
    }
    
	def delete() {
		def usr = User.get(params.username)
		usr.delete()
		return
	}
	
    def home() {
        if (needsAuth()) { return }
        
		def catlist = Category.list(sort: 'name').collect { it.name.capitalize() }
		def teamlist = Team.list().collect { it.name.capitalize() }

        def team = User.findByUsername(session.user).team
		def teamname = team.name
        def testruns = team.findTestRuns()
        if (testruns.size() > 5) {
            testruns = testruns[0..4]
        }
		
		def userlist = User.list()
		def usercount = User.findAll().size()
		int offset = 0
		int max    = 5
	
		if (params.offset) {
			offset = params.offset.toInteger()
			max    = params.max.toInteger()
		}
		
		int end = offset + max - 1
		if (end >= usercount) {
			end = usercount - 1
		}
	
		userlist = userlist[offset..end]
		
		[activeView: 'home', catlist: catlist, userlist: userlist, teamlist: teamlist, testruns: testruns, team: teamname, usercount: usercount]
    }
    
	def assignteam() {
		def usr = User.get(params.uid.toLong())
		def team = Team.findByName(params.selectedteam.toLowerCase())

		team.addToUsers(usr)
		team.save(failOnError:true)
		redirect (action: 'home')
	}
	
    private void createDefaultTestCaseFor(team, user) {
        def googleScript = '''\
package simtester.agent
import geb.*
import groovyx.net.http.ContentType
class AgentScript {
  static runtest(args) {
    def log = args.logger
    def sutAddr = 'http://www.google.com/'
    def sut = new RESTCli(args, sutAddr, ContentType.HTML)
    Browser.drive {
      go sutAddr
      log.info("Title: $title")
      assert 'Google' == title
      5.times {
        2.times { sut.get(path: '') }
        sleep 500
        sut.get(path: '')
      }
    }
  }
}'''
        
        def failingScript = '''\
package simtester.agent
import geb.*
import groovyx.net.http.ContentType
class AgentScript {
  static runtest(args) {
    def log = args.logger
    def sutAddr = 'http://www.google.com/'
    def sut = new RESTCli(args, sutAddr, ContentType.HTML)
    Browser.drive {
      go sutAddr
      log.info("Title: $title")
      assert 'Google' == title
      10.times { sut.get(path: '') }
      def number = 2
      assert number == 10
    }
  }
}'''

    def allRestScript = '''\
package simtester.agent
import geb.*
import groovyx.net.http.ContentType
class AgentScript {
  static runtest(args) {
    def log = args.logger
    def sutAddr = 'http://www.google.com/'
    def sut = new RESTCli(args, sutAddr, ContentType.HTML)
    Browser.drive {
      go sutAddr
      log.info("Title: $title")
      assert 'Google' == title
      3.times {
        4.times { sut.fakeget(path: '') }
        3.times { sut.fakepost(path: 'search') }
        2.times { sut.fakeput(path: 'code') }
        2.times { sut.fakedelete(path: 'spring') }
      }
    }
  }
}'''

        def tests = [
            'DefaultGoogleTest': googleScript,
            'FailingGoogleTest': failingScript,
            'AllRESTTest':       allRestScript
        ]

        tests.each { name, script ->
            if (!TestCase.findByNameAndTeam(name, team)) {
                def tc = new TestCase(name: name, type: 'GUI', script: script, owner: user)
                team.addToTestcases(tc)
            }
        }

        team.save(flush:true, failOnError:true)
    }
    
    private boolean needsAuth() {
        if (!session.user) {
            redirect (controller: 'user', action: 'index')
            return true
        }
        return false
    }
}
